package com.company.huisuo.widget

import android.content.Context
import android.graphics.Canvas
import android.graphics.drawable.Drawable
import android.util.AttributeSet
import android.view.MotionEvent
import android.view.View
import androidx.core.content.ContextCompat
import com.company.huisuo.R
import com.company.huisuo.ext.dp2px
import kotlin.math.min

/**
 * 自定义星级评分View
 * 支持触摸选择评分
 */
class RatingStarView @JvmOverloads constructor(
    context: Context,
    attrs: AttributeSet? = null,
    defStyleAttr: Int = 0
) : View(context, attrs, defStyleAttr) {

    // 星星总数
    private var starCount = 5

    // 当前评分
    private var rating = 0f
        set(value) {
            field = value.coerceIn(0f, starCount.toFloat())
            invalidate()
            onRatingChangeListener?.invoke(field)
        }

    // 星星大小（dp）
    private val starSize = 16.dp2px()

    // 星星间距（dp）
    private val starSpacing = 3.dp2px()

    // 亮色星星drawable
    private var starLightDrawable: Drawable? = null

    // 暗色星星drawable
    private var starDarkDrawable: Drawable? = null

    // 是否可点击
    private var isClickable = true

    // 评分变化监听
    private var onRatingChangeListener: ((Float) -> Unit)? = null

    init {
        // 加载星星图片
        starLightDrawable = ContextCompat.getDrawable(context, R.drawable.ic_feedback_start_1)
        starDarkDrawable = ContextCompat.getDrawable(context, R.drawable.ic_feedback_start_2)

        // 读取自定义属性
        context.obtainStyledAttributes(attrs, R.styleable.RatingStarView).apply {
            starCount = getInt(R.styleable.RatingStarView_starCount, 5)
            rating = getFloat(R.styleable.RatingStarView_rating, 0f)
            isClickable = getBoolean(R.styleable.RatingStarView_ratingClickable, true)
            recycle()
        }
    }

    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
        // 计算View宽度：星星总宽度 + 间距总宽度
        val totalWidth = starCount * starSize + (starCount - 1) * starSpacing
        val totalHeight = starSize

        setMeasuredDimension(totalWidth, totalHeight)
    }

    override fun onDraw(canvas: Canvas) {
        super.onDraw(canvas)

        var left = 0

        for (i in 0 until starCount) {
            val drawable = if (i < rating.toInt()) {
                starLightDrawable
            } else {
                starDarkDrawable
            }

            drawable?.setBounds(left, 0, left + starSize, starSize)
            drawable?.draw(canvas)

            left += starSize + starSpacing
        }
    }

    override fun onTouchEvent(event: MotionEvent): Boolean {
        if (!isClickable) {
            return super.onTouchEvent(event)
        }

        when (event.action) {
            MotionEvent.ACTION_DOWN,
            MotionEvent.ACTION_MOVE -> {
                // 根据触摸位置计算评分
                val touchX = event.x
                val newRating = calculateRating(touchX)
                if (newRating != rating) {
                    rating = newRating
                }
                return true
            }
            MotionEvent.ACTION_UP -> {
                performClick()
                return true
            }
        }

        return super.onTouchEvent(event)
    }

    override fun performClick(): Boolean {
        super.performClick()
        return true
    }

    /**
     * 根据触摸位置计算评分
     */
    private fun calculateRating(touchX: Float): Float {
        // 每个星星的总宽度（包含间距）
        val starTotalWidth = starSize + starSpacing

        // 计算触摸位置对应的星星索引
        val starIndex = (touchX / starTotalWidth).toInt()

        // 限制在有效范围内
        return min(starIndex + 1, starCount).toFloat()
    }

    /**
     * 更新评分
     */
    fun updateRating(newRating: Float) {
        this.rating = newRating
    }

    /**
     * 获取当前评分
     */
    fun getCurrentRating(): Float {
        return rating
    }

    /**
     * 设置星星总数
     */
    fun setStarCount(count: Int) {
        this.starCount = count
        requestLayout()
    }

    /**
     * 设置是否可点击
     */
    fun setRatingClickable(clickable: Boolean) {
        this.isClickable = clickable
    }

    /**
     * 设置评分变化监听
     */
    fun setOnRatingChangeListener(listener: (Float) -> Unit) {
        this.onRatingChangeListener = listener
    }
}
